<template>
  <div id="app">
    <keep-alive :include="['layout']">
      <router-view/>
    </keep-alive>
    <audio :src="playedSong.url" autoplay ref="audio"></audio>
  </div>
</template>

<script>
import { mapState } from 'vuex'
import { getMusicUrlApi, getSongDetail, getIsSongStatus } from '@/api/music'
import { Toast } from 'vant'

export default {
  name: 'App',
  components: {
    [Toast.name]: Toast
  },
  data () {
    return {
      // 要播放歌曲的对象
      playedSong: {},
      musicEndTimer: null,
      isNextSong: true
    }
  },
  computed: {
    ...mapState(['loginData', 'playingSongList', 'playedSongObj', 'playedSongIndex', 'audio', 'isPlayStatus', 'playedSongId'])
  },
  watch: {
    // playedSongObj 发生变化证明要播放歌曲，故，请求歌曲的 URL
    playedSongObj: function () {
      if (this.isSongStatus()) {
        Toast.clear()
        this.playMusicMethod()
      }
    },
    playedSongId: async function () {
      // 改变 playedSongObj 的值
      const { data } = await getSongDetail({
        id: this.playingSongList[this.playedSongIndex].id,
        cookie: this.loginData.cookie
      })
      this.$store.commit('setPlayedSongObj', data.songs[0])
    },
    playedSongIndex: function (newValue, oldValue) {
      newValue > oldValue ? this.isNextSong = true : this.isNextSong = false
      this.$store.commit('setPlayedSongId', this.playingSongList[this.playedSongIndex].id)
    },
    // 监视播放状态，暂停：清除定时器，播放：加载定时器
    isPlayStatus: function () {
      if (this.isPlayStatus === true && this.playedSong) {
        this.musicEndTimer = this.playMusicTimer()
      } else {
        clearInterval(this.musicEndTimer)
      }
    }
  },
  mounted () {
    this.$store.commit('setAudio', this.$refs.audio)
  },
  methods: {
    async playMusicMethod () {
      const { data } = await getMusicUrlApi({
        id: this.playingSongList[this.playedSongIndex].id,
        cookie: this.loginData.cookie
      })
      this.playedSong = data.data[0]
      this.musicEndTimer = this.playMusicTimer()
    },

    // 定时器，计算歌曲播放的进度
    playMusicTimer () {
      clearInterval(this.musicEndTimer)
      this.$store.commit('setPlayStatus', true)
      return setInterval(() => {
        if (this.audio.ended) {
          clearInterval(this.musicEndTimer)
          this.$store.commit('setPlayStatus', false)
          this.isNextSong = true
          this.next()
        } else {
          const timeRanges = this.audio.buffered
          this.$store.commit('setStep', this.audio.currentTime / this.audio.duration * 100)
          this.$store.commit('setCountDown', Math.floor(this.audio.duration) - Math.floor(this.audio.currentTime))
          this.$store.commit('setBufferBrogressBar', parseInt(timeRanges.end(timeRanges.length - 1) * 100 / this.audio.duration * 100 / 100))
        }
      }, 1000)
    },

    // 播放下一首歌曲
    next () {
      let songIndex = this.playedSongIndex
      // 后续没有歌曲列表，从第一首开始播放
      if (this.playedSongIndex === this.playingSongList.length) {
        this.$store.commit('setPlayedSongIndex', 0)
      }
      // 判断播放顺序；目的：解决播放上一曲时，如连续遇到多首无版权音乐，使其持续播放上一曲
      // 清除：歌曲成功播放后，会使 isNextSong 为 true，则播放顺序为下一曲
      this.isNextSong
        ? this.$store.commit('setPlayedSongIndex', songIndex += 1)
        : this.$store.commit('setPlayedSongIndex', songIndex -= 1)
    },
    async isSongStatus () {
      try {
        const { data } = await getIsSongStatus({
          id: this.playedSongObj.id
        })
        return data.success
      } catch (error) {
        Toast('无版权')
        const timer = setTimeout(() => {
          this.next()
          clearTimeout(timer)
        }, 1500)
      }
    }
  }
}
</script>

<style lang="less"></style>
